package com.ynet.middleground.user.model;

import java.time.LocalDateTime;
import java.util.List;
import java.util.Optional;
import java.util.stream.Collectors;

import org.apache.commons.lang3.StringUtils;
import org.dozer.Mapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.ynet.core.common.BaseReqObjPager;
import com.ynet.core.common.PagerInfo;
import com.ynet.core.exception.BusinessException;
import com.ynet.middleground.user.bean.*;
import com.ynet.middleground.user.dao.ChannelCompanyMapper;
import com.ynet.middleground.user.dto.ChannelCompanyDTO;
import com.ynet.middleground.user.dto.ChannelDTO;
import com.ynet.middleground.user.entity.ChannelCompany;
import com.ynet.middleground.user.entity.ChannelConfig;
import com.ynet.middleground.user.utils.BeanUtil;

/**
 * @author liulx
 * @description 渠道及对应公司处理模块
 * @date 2020-07-01 14:29
 */
@Component
public class ChannelCompanyModel extends ServiceImpl<ChannelCompanyMapper, ChannelCompany> {

    @Autowired
    private Mapper mapper;

    @Autowired
    private ChannelConfigModel channelConfigModel;

    /**
     * 检查公司是否重复
     * 
     * @param companyCode 公司编码
     * @param companyName 公司名称
     */
    public void checkRepeatCompany(String companyCode, String companyName) {
        LambdaQueryWrapper<ChannelCompany> queryWrapper = new LambdaQueryWrapper<>();
        if (StringUtils.isNotBlank(companyCode)) {
            queryWrapper.eq(ChannelCompany::getIsDeleted, "0");
            queryWrapper.eq(ChannelCompany::getCompanyCode, companyCode);
            int count = this.count(queryWrapper);
            if (count > 0) {
                throw new BusinessException("公司编号重复", "ECUC0200");
            }
        }
        if (StringUtils.isNotBlank(companyName)) {
            queryWrapper = new LambdaQueryWrapper<>();
            queryWrapper.eq(ChannelCompany::getIsDeleted, "0");
            queryWrapper.eq(ChannelCompany::getCompanyName, companyName);
            int count = this.count(queryWrapper);
            if (count > 0) {
                throw new BusinessException("公司名称重复", "ECUC0201");
            }
        }
    }

    /**
     * 检查渠道-公司对应关系是否已存在
     * 
     * @param channelId 渠道 id
     * @param companyCode 公司编码
     */
    public void checkRepeatChannelCompany(Integer channelId, String companyCode) {
        LambdaQueryWrapper<ChannelCompany> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(ChannelCompany::getIsDeleted, "0");
        queryWrapper.eq(ChannelCompany::getChannelId, channelId);
        queryWrapper.eq(ChannelCompany::getCompanyCode, companyCode);
        int count = this.count(queryWrapper);
        if (count > 0) {
            throw new BusinessException("渠道代码和公司代码对应关系已存在，请重新输入。", "ECUC0202");
        }
    }

    /**
     * 添加公司
     *
     * @param req 添加渠道关联公司请求对象
     * @return 添加成功后的公司 id
     */
    @Transactional(rollbackFor = Exception.class)
    public Integer add(AddChannelCompanyReq req) {
        // 校验公司信息是否重复
        // checkRepeatCompany(req.getCompanyCode(), req.getCompanyName());
        // 校验渠道和公司对应关系是否已存在
        checkRepeatChannelCompany(req.getChannelId(), req.getCompanyCode());
        ChannelConfig channel = channelConfigModel.getById(req.getChannelId());
        if (channel == null || channel.getIsDeleted()) {
            throw new BusinessException("该渠道信息不存在", "ECUC0102");
        }
        ChannelCompany channelCompany = mapper.map(req, ChannelCompany.class);
        channelCompany.setGmtCreate(LocalDateTime.now());
        channelCompany.setCreateBy(req.getOperationUserId());
        channelCompany.setGmtModified(LocalDateTime.now());
        channelCompany.setModifiedBy(req.getOperationUserId());
        this.save(channelCompany);
        return channelCompany.getId();
    }

    /**
     * 修改渠道关联公司
     * 
     * @param req 修改渠道关联公司请求对象
     */
    @Transactional(rollbackFor = Exception.class)
    public void modify(UpdateChannelCompanyReq req) {
        ChannelCompany company = this.getById(req.getId());
        if (company == null || company.getIsDeleted()) {
            throw new BusinessException("该公司信息不存在", "ECUC0203");
        }
        LambdaQueryWrapper<ChannelCompany> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(ChannelCompany::getIsDeleted, "0");
        queryWrapper.eq(ChannelCompany::getCompanyName, req.getCompanyName());
        List<ChannelCompany> channelCompanies = this.list(queryWrapper);
        if (channelCompanies != null) {
            if (channelCompanies.size() > 1) {
                throw new BusinessException("公司名称重复", "ECUC0201");
            }
            if (channelCompanies.size() == 1) {
                ChannelCompany existCompany = channelCompanies.get(0);
                if (!existCompany.getId().equals(req.getId())) {
                    throw new BusinessException("公司名称重复", "ECUC0201");
                }
            }
        }

        mapper.map(req, company);
        company.setGmtModified(LocalDateTime.now());
        company.setModifiedBy(req.getOperationUserId());
        this.updateById(company);
        // 更新条件
        LambdaUpdateWrapper<ChannelCompany> updateWrapper = new LambdaUpdateWrapper<>();
        updateWrapper.eq(ChannelCompany::getCompanyCode, company.getCompanyCode());
        ChannelCompany channelCompany1 = new ChannelCompany();
        channelCompany1.setCompanyName(req.getCompanyName());
        this.update(channelCompany1,updateWrapper);
    }

    /**
     * 根据关联公司 id 查询详情
     * 
     * @param req 查询基础对象
     * @return 渠道关联公司信息传输对象
     */
    public ChannelCompanyDTO getDetailById(QueryBaseReq req) {
        ChannelCompany company = this.getById(req.getId());
        if (company == null || company.getIsDeleted()) {
            throw new BusinessException("该公司信息不存在", "ECUC0203");
        }
        return mapper.map(company, ChannelCompanyDTO.class);
    }

    /**
     * 根据关联公司代码查询详情
     * 
     * @param req 查询渠道公司关系详情请求对象
     * @return 渠道关联公司信息传输对象
     */
    public ChannelCompanyDTO getDetailByCompanyCode(QueryChannelCompanyReq req) {
        LambdaQueryWrapper<ChannelCompany> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(ChannelCompany::getIsDeleted, "0");
        queryWrapper.eq(ChannelCompany::getCompanyCode, req.getCompanyCode());
        queryWrapper.last("limit 1");
        ChannelCompany company = this.getOne(queryWrapper);
        if (company == null || company.getIsDeleted()) {
            throw new BusinessException("该公司信息不存在", "ECUC0203");
        }
        return mapper.map(company, ChannelCompanyDTO.class);
    }

    /**
     * 根据公司 id 逻辑删除该信息
     * 
     * @param req 查询基础对象
     */
    @Transactional(rollbackFor = Exception.class)
    public void deleteCompany(QueryBaseReq req) {
        ChannelCompany company = this.getById(req.getId());
        if (company == null || company.getIsDeleted()) {
            throw new BusinessException("该公司信息不存在", "ECUC0203");
        }
        company.setIsDeleted(true);
        this.updateById(company);
    }

    /**
     * 分页查询渠道关联的公司列表
     * 
     * @param req 基础参数分页
     * @return 渠道关联公司列表
     */
    public List<ChannelCompanyDTO> listPage(BaseReqObjPager req) {
        PagerInfo pagerInfo = req.getPagerInfo();
        LambdaQueryWrapper<ChannelCompany> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(ChannelCompany::getIsDeleted, "0");
        Page<ChannelCompany> page = new Page<>(pagerInfo.getPageNum(), pagerInfo.getPageSize());
        IPage<ChannelCompany> iPage = this.page(page, queryWrapper);
        List<ChannelCompany> list = iPage.getRecords();
        pagerInfo.setTotal(iPage.getTotal());
        List<ChannelCompanyDTO> dtos = BeanUtil.mapList(mapper, list, ChannelCompanyDTO.class);
        dtos = dtos.stream().peek(dto -> {
            ChannelConfig channel = channelConfigModel.getById(dto.getChannelId());
            dto.setChannelDTO(mapper.map(channel, ChannelDTO.class));
        }).collect(Collectors.toList());
        return dtos;
    }

    /**
     * 查询渠道对应公司
     * 
     * @param req 查询渠道详情请求对象
     * @return 渠道关联公司信息列表
     */
    public List<ChannelCompanyDTO> companyListByChannelCode(QueryChannelReq req) {
        LambdaQueryWrapper<ChannelConfig> channelConfigWrapper = new LambdaQueryWrapper<>();
        channelConfigWrapper.eq(ChannelConfig::getIsDeleted, "0");
        channelConfigWrapper.eq(ChannelConfig::getChannelCode, req.getChannelCode());
        ChannelConfig channelConfig = channelConfigModel.getOne(channelConfigWrapper);
        Optional.ofNullable(channelConfig).orElseThrow(() -> new BusinessException("该渠道信息不存在", "ECUC0102"));
        ChannelDTO channelDdo = mapper.map(channelConfig, ChannelDTO.class);
        Integer channelId = channelConfig.getId();
        LambdaQueryWrapper<ChannelCompany> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(ChannelCompany::getIsDeleted, "0");
        queryWrapper.eq(ChannelCompany::getChannelId, channelId);
        List<ChannelCompany> channelCompanyReqList = this.list(queryWrapper);
        List<ChannelCompanyDTO> dtoList = BeanUtil.mapList(mapper, channelCompanyReqList, ChannelCompanyDTO.class);
        dtoList = dtoList.stream().peek(com -> com.setChannelDTO(channelDdo)).collect(Collectors.toList());
        return dtoList;
    }

}
